home *** CD-ROM | disk | FTP | other *** search
/ Large Pack of OldSkool DOS MOD Trackers / package_16-january-2001.zip / Effects / cheapo negative.cpp < prev    next >
C/C++ Source or Header  |  2000-08-01  |  7KB  |  351 lines

  1. // Copyright (C) Mikko Apo (apo@iki.fi)
  2. // The following code may be used to write free software
  3. // if credit is given to the original author.
  4. // Using it for anything else is not allowed without permission
  5. // from the author.
  6.  
  7.  
  8. #include <stdlib.h>
  9. #include <time.h>
  10. #include <math.h>
  11. #include <string.h>
  12. #include "../mdk.h"
  13.  
  14. #define COMMAND_STRING "About..."
  15. #define MACHINE_NAME "cheapo negative"
  16. #define SHORT_NAME "ch.neg"
  17. #define MACHINE_AUTHOR "Mikko Apo (apo@iki.fi)"
  18. #define MAX_TRACKS        0
  19. #define MIN_TRACKS        0
  20. #define NUMGLOBALPARAMETERS 5
  21. #define NUMTRACKPARAMETERS 0
  22. #define NUMATTRIBUTES 0
  23. #define __VERSION__ "1.0"
  24.  
  25. //    Parameters
  26.  
  27. CMachineParameter const paraMode = 
  28. { pt_byte, "Stereo Mode","Stereo Control Mode: 0 Separate channels, 1 Left master, right slave",0,1,0xff,MPF_STATE,0 };
  29.  
  30. CMachineParameter const paraLGain = 
  31. { pt_byte, "Left Gain","Left Gain",0,0xfe,0xff,MPF_STATE,0xfe };
  32.  
  33. CMachineParameter const paraRGain = 
  34. { pt_byte, "Right Gain","Right Gain",0,0xfe,0xff,MPF_STATE,0xfe };
  35.  
  36. CMachineParameter const paraInertia = 
  37. { pt_word, "Inertia","Inertia length",0,0xfffe,0xffff,MPF_STATE,1 };
  38.  
  39. CMachineParameter const paraInertiaUnit = 
  40. { pt_byte, "Inertia Unit","Inertia Unit: 0=tick (default), 1 ticks/256, 2 samples, 3=ms, 4=seconds",0,4,0xff,MPF_STATE,0 };
  41.  
  42. // List of all parameters, track parameters last
  43.  
  44. CMachineParameter const *pParameters[] = 
  45. { ¶Mode,¶LGain,¶RGain,¶Inertia,¶InertiaUnit };
  46.  
  47. #pragma pack(1)
  48.  
  49. class gvals
  50. {
  51. public:
  52.     byte mode;
  53.     byte lgain;
  54.     byte rgain;
  55.     word inertia;
  56.     byte inertiaunit;
  57. };
  58.  
  59. #pragma pack()
  60.  
  61. // Machine's info
  62.  
  63. CMachineInfo const MacInfo = 
  64. {
  65.     MT_EFFECT,MI_VERSION,MIF_DOES_INPUT_MIXING,MIN_TRACKS,MAX_TRACKS,
  66.     NUMGLOBALPARAMETERS,NUMTRACKPARAMETERS,pParameters,NUMATTRIBUTES,NULL,
  67. #ifdef _DEBUG
  68.     MACHINE_NAME" [DEBUG]"
  69. #else
  70.     MACHINE_NAME
  71. #endif
  72.     ,SHORT_NAME,MACHINE_AUTHOR,COMMAND_STRING
  73. };
  74.  
  75.  
  76. class miex : public CMDKMachineInterfaceEx
  77. {
  78.  
  79. };
  80.  
  81. class mi : public CMDKMachineInterface
  82. {
  83. public:
  84.     mi();
  85.  
  86.     virtual void Command(int const i);
  87.     virtual void Tick();
  88.     virtual char const *DescribeValue(int const param, int const value);
  89.  
  90.     virtual void MDKInit(CMachineDataInput * const pi);
  91.     virtual bool MDKWork(float *psamples, int numsamples, int const mode);
  92.     virtual bool MDKWorkStereo(float *psamples, int numsamples, int const mode);
  93.     virtual void MDKSave(CMachineDataOutput * const po) { }
  94.  
  95.     public:
  96.     virtual CMDKMachineInterfaceEx *GetEx() { return &ex; }
  97.     virtual void OutputModeChanged(bool stereo);
  98.  
  99.     public:
  100.     miex ex;
  101.     gvals gval;
  102.  
  103. private:
  104.  
  105.     unsigned long calculate_length(byte type, word len);
  106.  
  107.     float l_amp,r_amp;
  108.     int valInertia,valInertiaUnit;
  109.     bool l_inertia,r_inertia,first;    // inertia
  110.     float l_amp_inc,l_amp_target; //
  111.     float r_amp_inc,r_amp_target;  //
  112.     unsigned int l_counter,r_counter; //
  113.     int valMode;
  114. };
  115.  
  116.  
  117. DLL_EXPORTS
  118.  
  119. mi::mi()
  120. {
  121.     GlobalVals = &gval;
  122. }
  123.  
  124. void mi::Command(int const i)
  125. {
  126.     switch(i)
  127.     {
  128.     case 0:
  129.         pCB->MessageBox(MACHINE_NAME"\n\nBuild date: "__DATE__"\nVersion: "__VERSION__"\nCoded by: "MACHINE_AUTHOR"\nThanks to #buzzdev for support.\n\nCheck out http://www.iki.fi/apo/buzz/\nfor more buzz stuff.\n\nExcellent skin made by Hymax.");
  130.         break;
  131.     }
  132. }
  133.  
  134. char const *mi::DescribeValue(int const param, int const value)
  135. {
  136.     static char txt[100];
  137.  
  138.     switch(param)
  139.     {
  140.     case 0:
  141.         return((value)?"Right slave":"Separate");
  142.     case 1:
  143.     case 2:
  144.         sprintf(txt,"%.2f",((float)(value-0x7f))/0x7f);
  145.         break;
  146.     case 3:
  147.         sprintf(txt,"%d %s",value,DescribeValue(4,valInertiaUnit));
  148.         break;
  149.     case 4:
  150.         switch(value)
  151.         {
  152.         case 0: return("ticks");
  153.         case 1: return("ticks/256");
  154.         case 2:    return("samples");
  155.         case 3:    return("ms");
  156.         case 4: return("secs");
  157.         }
  158.         break;
  159.     }
  160.  
  161.     return txt;
  162. }
  163.  
  164. void mi::MDKInit(CMachineDataInput * const pi)
  165. {
  166.     valMode=paraMode.DefValue;
  167.     l_amp=((float)(paraLGain.DefValue-0x7f))/0x7f;
  168.     r_amp=((float)(paraRGain.DefValue-0x7f))/0x7f;
  169.     l_inertia=r_inertia=false;
  170.     valInertia=paraInertia.DefValue;
  171.     valInertiaUnit=paraInertiaUnit.DefValue;
  172.     first=true;
  173. }
  174.  
  175. void mi::OutputModeChanged(bool stereo)
  176. {
  177.     if(r_inertia)
  178.     {
  179.         r_amp=r_amp_target;
  180.         r_inertia=false;
  181.     }
  182. }
  183.  
  184. unsigned long mi::calculate_length(byte type, word len)
  185. {
  186.     unsigned long length;
  187.     switch(type)
  188.     {
  189.     case 0:
  190.         length=len*pMasterInfo->SamplesPerTick;
  191.         break;
  192.     case 1:
  193.         length=(len*pMasterInfo->SamplesPerTick)/256;
  194.         break;
  195.     case 2:
  196.         length=len;
  197.         break;
  198.     case 3:
  199.         length=(len*pMasterInfo->SamplesPerSec)/1000;
  200.         break;
  201.     case 4:
  202.         length=len*pMasterInfo->SamplesPerSec;
  203.         break;
  204.     }
  205.     return length;
  206. }
  207.  
  208.  
  209. void mi::Tick()
  210. {
  211.   if (gval.mode != paraMode.NoValue)
  212.   {
  213.     if(valMode!=gval.mode)
  214.     {
  215.         if(r_inertia)
  216.         {
  217.             r_amp=r_amp_target;
  218.             r_inertia=false;
  219.         }
  220.     }
  221.     valMode=gval.mode;
  222.   }
  223.   if (gval.inertia != paraInertia.NoValue)
  224.   {
  225.     valInertia=gval.inertia;
  226.   }
  227.   if (gval.inertiaunit != paraInertiaUnit.NoValue)
  228.   {
  229.     valInertiaUnit=gval.inertiaunit;
  230.   }
  231.  
  232.   if(first)
  233.   {
  234.     if (gval.lgain != paraLGain.NoValue)
  235.     {
  236.         l_amp=((float)(gval.lgain-0x7f))/0x7f;
  237.     }
  238.     if (gval.rgain != paraRGain.NoValue)
  239.     {
  240.         r_amp=((float)(gval.rgain-0x7f))/0x7f;
  241.     }
  242.   }
  243.   else
  244.   {
  245.     if (gval.lgain != paraLGain.NoValue)
  246.     {
  247.         l_inertia=true;
  248.         l_counter=calculate_length(valInertiaUnit,valInertia);
  249.         l_amp_target=((float)(gval.lgain-0x7f))/0x7f;
  250.         l_amp_inc=(l_amp_target-l_amp)/l_counter;
  251.     }
  252.     if (gval.rgain != paraRGain.NoValue)
  253.     {
  254.         r_inertia=true;
  255.         r_counter=calculate_length(valInertiaUnit,valInertia);
  256.         r_amp_target=((float)(gval.rgain-0x7f))/0x7f;
  257.         r_amp_inc=(r_amp_target-r_amp)/r_counter;
  258.     }
  259.   }
  260.  
  261.   first=false;
  262.  
  263.  
  264. bool mi::MDKWorkStereo(float *psamples, int numsamples, int const mode)
  265. {
  266.     if ((mode==WM_WRITE)||(mode==WM_NOIO))
  267.     {
  268.         return false;
  269.     }
  270.  
  271.     if (mode == WM_READ)        // <thru>
  272.         return true;
  273.  
  274.     if(valMode)
  275.     {
  276.     do 
  277.     {
  278.         if(l_inertia)
  279.         {
  280.             l_amp+=l_amp_inc;
  281.             if(!(l_counter--))
  282.             {
  283.                 l_inertia=false;
  284.                 l_amp=l_amp_target;
  285.             }
  286.         }
  287.         psamples[0]*=l_amp;
  288.         psamples[1]*=l_amp;
  289.         psamples+=2;
  290.     } while(--numsamples);
  291.     } else
  292.     {
  293.  
  294.     do 
  295.     {
  296.         if(l_inertia)
  297.         {
  298.             l_amp+=l_amp_inc;
  299.             if(!(l_counter--))
  300.             {
  301.                 l_inertia=false;
  302.                 l_amp=l_amp_target;
  303.             }
  304.         }
  305.         psamples[0]*=l_amp;
  306.         if(r_inertia)
  307.         {
  308.             r_amp+=r_amp_inc;
  309.             if(!(r_counter--))
  310.             {
  311.                 r_inertia=false;
  312.                 r_amp=r_amp_target;
  313.             }
  314.         }
  315.         psamples[1]*=r_amp;
  316.         psamples+=2;
  317.     } while(--numsamples);
  318.     }
  319.  
  320.     return true;
  321. }
  322.  
  323. bool mi::MDKWork(float *psamples, int numsamples, int const mode)
  324. {
  325.     if ((mode==WM_WRITE)||(mode==WM_NOIO))
  326.     {
  327.         return false;
  328.     }
  329.  
  330.     if (mode == WM_READ)        // <thru>
  331.         return true;
  332.  
  333.     do 
  334.     {
  335.         if(l_inertia)
  336.         {
  337.             l_amp+=l_amp_inc;
  338.             if(!(l_counter--))
  339.             {
  340.                 l_inertia=false;
  341.                 l_amp=l_amp_target;
  342.             }
  343.         }
  344.         psamples[0]*=l_amp;
  345.         psamples++;
  346.     } while(--numsamples);
  347.  
  348.     return true;
  349. }
  350.